#!/usr/bin/env python
# encoding: utf-8
# @author: Lin Han
# @contact: voldemort22@126.com
# @file: crud.py
# @time: 2021/4/12 13:25
# @desc:
import json
from datetime import datetime
from typing import Dict, Optional, List

from application.history_clamp.queryModels import KeywordFilter
from cache.redis_pool import get_redis
from models.queryModels import MultipleConditionQueryHistoryClamps
from utils.utils import is_contained_by_another_list
from views.configs import CATPART_OSS_ADDRESS, WORKPIECE_CATPART_OSS_ADDRESS
from views.crud import get_history_clamp_in_all_scene
from views.tag import clampTagInit


def keyword_search_history_clamp(
        queryModel: MultipleConditionQueryHistoryClamps,
        result: list,
) -> list:
    """
    列表查询多条历史夹具或历史零件。

    :param queryModel: 前端传过来的参数，原封不动地传过来。
    :param result: 事先从历史夹具的数据库中把所有数据都取出来，以供搜索使用。
    """
    filtered_result = []
    for i in result:
        i_time = datetime.strptime(i["time"], "%Y-%m-%d %H:%M")
        # 按关键字查询
        if queryModel.keyword is None or queryModel.keyword.lower() in i["number"].lower() or queryModel.keyword.lower() in i["name"].lower():
            if queryModel.isFlag is None or not queryModel.isFlag or queryModel.isFlag == i['isFlag']:
                if queryModel.isFeature is None or not queryModel.isFeature or queryModel.isFeature == i['isFeature']:
                    if queryModel.standard is None or queryModel.standard in i['tag']['standard']:
                        if queryModel.startTime is None or queryModel.startTime < i_time:
                            if queryModel.endTime is None or i_time < queryModel.endTime:
                                if queryModel.hasPin is None or not queryModel.hasPin or queryModel.hasPin == i['tag']['hasPin']:
                                    if queryModel.hasStopBlock is None or not queryModel.hasStopBlock or queryModel.hasStopBlock == i['tag']['hasStopBlock']:
                                        if queryModel.area is None or not queryModel.area or queryModel.area == i['tag']['area']:
                                            if queryModel.numbers is None or i["number"] in queryModel.numbers:

                                                try:
                                                    if None is i["tag"]["airNumber"]:
                                                        i["tag"]["airNumber"] = 0
                                                except:
                                                    i["tag"]["airNumber"] = 0

                                                try:
                                                    if None is i["tag"]["rpsNumber"]:
                                                        i["tag"]["rpsNumber"] = 0
                                                except:
                                                    i["tag"]["rpsNumber"] = 0
                                                try:
                                                    if None is i["tag"]["rpsType"]:
                                                        i["tag"]["rpsType"] = []
                                                except:
                                                    i["tag"]["rpsType"] = []

                                                if is_contained_by_another_list(queryModel.rpsType, i["tag"]["rpsType"]):
                                                    filtered_result.append(i)
    return sorted(filtered_result, key=lambda x: x["name"])


def keyword_search_history_clamp_v2(
        queryModel: MultipleConditionQueryHistoryClamps,
        result: list,
) -> list:
    """
    新版的关键字搜索功能，不需要再写十几行的if来判断了。

    :param queryModel:
    :param result:
    :return:
    """
    result = [j for j in result if queryModel.dict()["startTime"] <= datetime.strptime(j["time"], "%Y-%m-%d %H:%M") <= queryModel.dict()["endTime"]]
    queryModel = KeywordFilter(**queryModel.dict())
    # 先判断queryModel里面的每个键，如果键对应的值为None就跳过；如果键名为keyword也跳过（在下一步判断）
    for i in queryModel.dict().keys():
        if queryModel.dict()[i] is None or i == "keyword":
            continue
        elif i == "numbers":
            result = [j for j in result if j["number"] in queryModel.dict()[i]]
        elif i == "rpsType":
            result = [j for j in result if is_contained_by_another_list(queryModel.dict()[i], j["tag"][i])]
        else:
            result = [j for j in result if j["tag"][i] == queryModel.dict()[i]]
    filtered_result = []
    for i in result:
        if queryModel.keyword is None or queryModel.keyword in i["number"] or queryModel.keyword.lower() in i["name"].lower() or queryModel.keyword.lower() in i["tag"]["area"].lower():
            filtered_result.append(i)
    return sorted(filtered_result, key=lambda x: x["name"])


def generate_history_clamp_data(
        number: str,
        file_path: str,
        workpiece_file_path: Optional[str] = None,
        desc: str = "",
        version: str = "1.0",
        isFeature: bool = False,
        isFlag: bool = False,
) -> Dict:
    """

    :param file_path: 夹具在OSS上的地址
    :param number:
    :param workpiece_file_path: 工件在OSS上的地址
    :param isFlag:
    :param isFeature:
    :param desc:
    :param version:
    """
    model = {
        "number": number,
        "time": datetime.now().strftime("%Y-%m-%d %H:%M"),
        # 存到数据库的name字段只应当包含最后一层的名字
        "name": file_path.split("/")[-1],
        "desc": desc,
        "type": "1",
        "version": version,
        "isFeature": isFeature,
        "isFlag": isFlag,
        "tag": clampTagInit(),
        "related": {
            "standardClamp": [],
        },
        "file": {
            CATPART_OSS_ADDRESS: file_path,
            "transferFormatMessage": "not transfered yet",
        },
    }

    # 对历史夹具，由于还有绑定工件，如果工件的OSS路径不为空的话，也把它添加到model中
    if workpiece_file_path is not None:
        model["file"][WORKPIECE_CATPART_OSS_ADDRESS] = workpiece_file_path

    return model


def retrieve_all_history_clamp_redis_values() -> List:
    """

    :return: 从redis中拿到的历史夹具数据
    """
    redis = get_redis()
    history_clamp_numbers = redis.keys("202101[0-9]*")
    history_clamps = redis.mget(history_clamp_numbers)
    result = []
    for i in history_clamps:
        result.append(json.loads(i))
    return result


def retrieve_all_scene_redis_values() -> List:
    """

    :return: 从redis中拿到的所有场景数据
    """
    redis = get_redis()
    # scene_numbers = redis.keys("202106[0-9]*")
    # scenes = redis.mget(scene_numbers)
    # result = []
    # for i in scenes:
    #     result.append(json.loads(i))
    # return result
    scene_numbers = redis.get("scene")
    scene_numbers = json.loads(scene_numbers)
    scenes = redis.mget(*scene_numbers)
    return [json.loads(i) for i in scenes if i is not None]


def retrieve_one_redis_value(number: str):
    """

    :return: 从redis中拿到的一条历史夹具数据
    """
    redis = get_redis()
    history_clamp = redis.get(number)
    return json.loads(history_clamp)


def retrieve_one_scene_redis_value(scene_number: str):
    """

    :return: 从redis中拿到的一条场景数据
    """
    redis = get_redis()
    scene = redis.get(scene_number)
    return json.loads(scene)


def get_history_clamp_in_assigned_scene(scene_number: str):
    # 获取特定场景中包含的所有历史夹具的id
    scene = retrieve_one_scene_redis_value(scene_number)
    return scene["historyClamp"]


def get_standard_clamp_by_history_clamp(history_clamp_number: str) -> List:
    history_clamp = retrieve_one_redis_value(history_clamp_number)
    return history_clamp["related"]["standardClamp"]


def is_scene_binded_history_clamp(number: str):
    """
    判断这个历史夹具是否包含任何一个场景中，是的话返回True，否则返回False

    :param number: 历史夹具的编号
    """
    history_clamp_in_scene = get_history_clamp_in_all_scene()
    if number in history_clamp_in_scene:
        return True
    else:
        return False

# if __name__ == '__main__':
# print(retrieve_redis_values(["2021060000008009", "2021060000009010"]))
# print(get_history_clamp_in_all_scene())
# print(retrieve_redis_values(["2222222222222222", "2021060000009010"]))
